package com.edu.exam.entity.grading;

import com.edu.exam.enums.grading.GradingStatus;
import com.edu.exam.enums.grading.ValidationStatus;
import com.edu.exam.enums.grading.GradeType;
import com.edu.exam.enums.grading.GradeScoreType;
import com.edu.exam.enums.grading.EntryMethod;
import com.edu.exam.enums.grading.EntrySource;
import com.edu.exam.enums.status.grade.GradeStatus;
import jakarta.persistence.*;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.data.annotation.CreatedDate;
import org.springframework.data.annotation.LastModifiedDate;
import org.springframework.data.jpa.domain.support.AuditingEntityListener;

import java.math.BigDecimal;
import java.time.LocalDateTime;

/**
 * 成绩录入实体类
 * [所属模块] G-01 成绩录入模块
 *
 * <p>成绩录入实体用于存储学生成绩的核心数据，包含
 * 成绩基本信息、录入状态、操作追踪、审核状态等。确保成绩数据的完整性和可追溯性。</p>
 *
 * <p>核心功能：
 * - 成绩存储：存储学生的成绩分数和相关信息
 * - 状态管理：管理成绩的录入和审核状态
 * - 操作追踪：记录录入操作的时间和人员
 * - 批次管理：支持批量录入的批次标识
 * - 备注管理：存储成绩的特殊说明信息</p>
 *
 * @author 系统生成
 * @version 1.0
 * @since 2025-11-10
 */
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
@Entity
@EntityListeners(AuditingEntityListener.class)
public class GradeEntry {

    /**
     * 主键ID
     */
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    /**
     * 学生ID
     *
     * <p>关联学生的唯一标识符。</p>
     */
    @Column(name = "student_id", nullable = false, length = 50)
    private String studentId;

    /**
     * 课程ID
     *
     * <p>关联课程的唯一标识符。</p>
     */
    @Column(name = "course_id", nullable = false, length = 50)
    private String courseId;

    /**
     * 成绩分数
     *
     * <p>学生的成绩分数，精确到小数点后两位。</p>
     */
    @Column(name = "score", nullable = false, precision = 10, scale = 2)
    private BigDecimal score;

    /**
     * 成绩类型
     *
     * <p>成绩的类型标识。
     * 支持的类型：DAILY（平时成绩）、MIDTERM（期中成绩）、FINAL（期末成绩）、QUIZ（测验）、ASSIGNMENT（作业）、OTHER（其他）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "grade_type", nullable = false, length = 20)
    private GradeType gradeType;

    /**
     * 成绩状态
     *
     * <p>成绩的当前状态。
     * 支持的状态：DRAFT（草稿）、PENDING_REVIEW（待审核）、UNDER_REVIEW（审核中）、APPROVED（已审核）、REJECTED（已拒绝）、PUBLISHED（已发布）、ARCHIVED（已归档）、LOCKED（已锁定）、MODIFIED（已修改）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "status", nullable = false, length = 20)
    private GradeStatus status = GradeStatus.DRAFT;

    /**
     * 录入用户ID
     *
     * <p>录入成绩的用户ID。</p>
     */
    @Column(name = "entry_user_id", nullable = false, length = 50)
    private String entryUserId;

    /**
     * 录入时间
     *
     * <p>成绩录入的时间。</p>
     */
    @Column(name = "entry_time", nullable = false)
    private LocalDateTime entryTime;

    /**
     * 成绩备注
     *
     * <p>成绩的特殊说明或备注信息。</p>
     */
    @Column(name = "comment", columnDefinition = "TEXT")
    private String comment;

    /**
     * 批次ID
     *
     * <p>批量录入的批次标识符，用于管理批量操作。</p>
     */
    @Column(name = "batch_id", length = 100)
    private String batchId;

    /**
     * 成绩分数类型
     *
     * <p>成绩分数的类型标识，用于区分不同的评分标准。
     * 支持的类型：PERCENTAGE（百分制）、LEVEL_4（四级制）、LEVEL_5（五级制）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "grade_score_type", length = 20)
    private GradeScoreType gradeScoreType;

    /**
     * 任务ID
     *
     * <p>关联的录入任务ID，用于任务驱动的成绩录入。</p>
     */
    @Column(name = "task_id", length = 50)
    private String taskId;

    /**
     * 审核用户ID
     *
     * <p>审核成绩的用户ID。</p>
     */
    @Column(name = "review_user_id", length = 50)
    private String reviewUserId;

    /**
     * 审核时间
     *
     * <p>成绩审核的时间。</p>
     */
    @Column(name = "review_time")
    private LocalDateTime reviewTime;

    /**
     * 审核意见
     *
     * <p>审核人员的意见和说明。</p>
     */
    @Column(name = "review_comment", columnDefinition = "TEXT")
    private String reviewComment;

    /**
     * 发布时间
     *
     * <p>成绩发布的时间。</p>
     */
    @Column(name = "publish_time")
    private LocalDateTime publishTime;

    /**
     * 修改次数
     *
     * <p>成绩修改的次数统计。</p>
     */
    @Column(name = "modify_count", nullable = false)
    private Integer modifyCount = 0;

    /**
     * 最后修改时间
     *
     * <p>成绩最后修改的时间。</p>
     */
    @Column(name = "last_modify_time")
    private LocalDateTime lastModifyTime;

    /**
     * 最后修改用户ID
     *
     * <p>最后修改成绩的用户ID。</p>
     */
    @Column(name = "last_modify_user_id", length = 50)
    private String lastModifyUserId;

    /**
     * 录入方式
     *
     * <p>成绩录入的方式。
     * 支持的方式：MANUAL（手动录入）、BATCH_IMPORT（批量导入）、AUTO_IMPORT（自动导入）、TEMP_SAVE（临时保存）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "entry_method", length = 20)
    private EntryMethod entryMethod = EntryMethod.MANUAL;

    /**
     * 录入来源
     *
     * <p>成绩录入的来源系统。
     * 支持的来源：WEB（网页端）、MOBILE（移动端）、API（接口）、SYSTEM（系统自动）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "entry_source", length = 20)
    private EntrySource entrySource = EntrySource.WEB;

    /**
     * 录入IP地址
     *
     * <p>录入操作时的IP地址。</p>
     */
    @Column(name = "entry_ip_address", length = 50)
    private String entryIpAddress;

    /**
     * 数据来源ID
     *
     * <p>原始数据的来源标识，用于数据溯源。</p>
     */
    @Column(name = "source_data_id", length = 100)
    private String sourceDataId;

    /**
     * 数据版本
     *
     * <p>成绩数据的版本号。</p>
     */
    @Column(name = "data_version", length = 20)
    private String dataVersion = "1.0";

    /**
     * 验证状态
     *
     * <p>成绩数据验证的状态。
     * 支持的状态：PENDING（待验证）、PASSED（通过）、FAILED（失败）、SKIPPED（跳过）</p>
     */
    @Enumerated(EnumType.STRING)
    @Column(name = "validation_status", length = 20)
    private ValidationStatus validationStatus = ValidationStatus.PENDING;

    /**
     * 验证结果
     *
     * <p>数据验证的结果详情，JSON格式存储。</p>
     */
    @Column(name = "validation_result", columnDefinition = "TEXT")
    private String validationResult;

    /**
     * 成绩标签
     *
     * <p>JSON格式的成绩标签，用于分类和过滤。</p>
     */
    @Column(name = "grade_tags", columnDefinition = "TEXT")
    private String gradeTags;

    /**
     * 成绩备注详情
     *
     * <p>详细的备注信息，JSON格式存储。</p>
     */
    @Column(name = "grade_details", columnDefinition = "TEXT")
    private String gradeDetails;

    // ===== 审计字段 =====

    /**
     * 创建时间
     */
    @CreatedDate
    @Column(name = "create_time", nullable = false, updatable = false)
    private LocalDateTime createTime;

    /**
     * 更新时间
     */
    @LastModifiedDate
    @Column(name = "update_time", nullable = false)
    private LocalDateTime updateTime;

    /**
     * 创建用户ID
     */
    @Column(name = "create_user_id", length = 50)
    private String createUserId;

    /**
     * 更新用户ID
     */
    @Column(name = "update_user_id", length = 50)
    private String updateUserId;

    /**
     * 是否删除
     */
    @Column(name = "is_deleted", nullable = false)
    private Boolean isDeleted = false;

    /**
     * 删除时间
     */
    @Column(name = "delete_time")
    private LocalDateTime deleteTime;

    /**
     * 删除用户ID
     */
    @Column(name = "delete_user_id", length = 50)
    private String deleteUserId;
}